﻿using System.Collections.Generic;
using System.Windows;
using System.Windows.Controls.Primitives;
using System.Linq;

namespace Gmantis.Controls.DataGrid
{
    internal class DataGridNewInputHandlingStrategy : DataGridDefaultInputHandlingStrategy
    {
        public DataGridNewInputHandlingStrategy(DataGrid dataGrid)
            : base(dataGrid)
        {
        }

        public IEnumerable<DataGridColumn> GetNextSelectableColumns(DataGridCell currentCell, GeneratorDirection direction)
        {
            DataGridCellsRange range = currentCell.DataGrid.Viewport.Range(currentCell);
            DataGridColumn currentColumn = (direction == GeneratorDirection.Forward) ? range.BottomRightCell.Column : range.TopLeftCell.Column;
            return this.GetNextSelectableColumns(currentColumn, direction);
        }

        public virtual IEnumerable<DataGridColumn> GetNextSelectableColumns(DataGridColumn currentColumn, GeneratorDirection direction)
        {
            DataGrid dataGrid = currentColumn.DataGrid;
            int fromColumnIndex = (direction == GeneratorDirection.Forward) ? (currentColumn.DisplayIndex + 1) : (currentColumn.DisplayIndex - 1);
            foreach (DataGridColumn iteratorVariable2 in dataGrid.Columns.GetVisibleColumnsFromIndex(fromColumnIndex, direction))
            {
                if (iteratorVariable2.IsSelectable)
                {
                    yield return iteratorVariable2;
                }
            }
        }

        public IEnumerable<DataGridRow> GetNextSelectableRows(DataGridCell currentCell, GeneratorDirection direction)
        {
            DataGridCellsRange range = currentCell.DataGrid.Viewport.Range(currentCell);
            DataGridRow currentRow = (direction == GeneratorDirection.Forward) ? range.BottomRightCell.Row : range.TopLeftCell.Row;
            return this.GetNextSelectableRows(currentRow, direction);
        }

        public virtual IEnumerable<DataGridRow> GetNextSelectableRows(DataGridRow currentRow, GeneratorDirection direction)
        {
            DataGrid dataGrid = currentRow.DataGrid;
            int fromRowIndex = (direction == GeneratorDirection.Forward) ? (currentRow.Index + 1) : (currentRow.Index - 1);
            foreach (DataGridRow iteratorVariable2 in dataGrid.Rows.GetVisibleRowsFromIndex(fromRowIndex, direction, false))
            {
                if (iteratorVariable2.IsSelectable)
                {
                    yield return iteratorVariable2;
                }
            }
        }

        public override bool GoToDownCell(DataGridCell currentCell, bool shift, bool ctrl)
        {
            if (currentCell == null)
            {
                return false;
            }
            DataGrid dataGrid = currentCell.DataGrid;
            DataGridRow row = this.GetNextSelectableRows(currentCell, GeneratorDirection.Forward).FirstOrDefault<DataGridRow>();
            if (row != null)
            {
                this.SetCurrentCell(dataGrid[row, currentCell.Column], shift, ctrl);
            }
            return true;
        }

        public override bool GoToLeftCell(DataGridCell currentCell, bool shift, bool ctrl)
        {
            if (currentCell == null)
            {
                return false;
            }
            DataGrid dataGrid = currentCell.DataGrid;
            DataGridRow row = currentCell.Row;
            foreach (DataGridColumn column in this.GetNextSelectableColumns(dataGrid.CurrentCell, GeneratorDirection.Backward))
            {
                if (row.HasCellPresenter(column))
                {
                    DataGridCell cell = dataGrid[row, column];
                    return this.SetCurrentCell(cell, KeyboardUtil.Shift, KeyboardUtil.Ctrl);
                }
            }
            if (row is DataGridGroupRow)
            {
                DataGridGroupRow row2 = row as DataGridGroupRow;
                if (row2.GroupRowsVisibility == Visibility.Visible)
                {
                    row2.GroupRowsVisibility = Visibility.Collapsed;
                }
            }
            return true;
        }

        public override bool GoToRightCell(DataGridCell currentCell, bool shift, bool ctrl)
        {
            if (currentCell == null)
            {
                return false;
            }
            DataGrid dataGrid = currentCell.DataGrid;
            DataGridRow row = currentCell.Row;
            if (row is DataGridGroupRow)
            {
                DataGridGroupRow row2 = row as DataGridGroupRow;
                if (row2.GroupRowsVisibility == Visibility.Collapsed)
                {
                    row2.GroupRowsVisibility = Visibility.Visible;
                    return true;
                }
            }
            foreach (DataGridColumn column in this.GetNextSelectableColumns(dataGrid.CurrentCell, GeneratorDirection.Forward))
            {
                if (row.HasCellPresenter(column))
                {
                    DataGridCell cell = dataGrid[row, column];
                    return this.SetCurrentCell(cell, KeyboardUtil.Shift, KeyboardUtil.Ctrl);
                }
            }
            return true;
        }

        public override bool GoToUpCell(DataGridCell currentCell, bool shift, bool ctrl)
        {
            if (currentCell == null)
            {
                return false;
            }
            DataGrid dataGrid = currentCell.DataGrid;
            DataGridRow row = this.GetNextSelectableRows(currentCell, GeneratorDirection.Backward).FirstOrDefault<DataGridRow>();
            if (row != null)
            {
                this.SetCurrentCell(dataGrid[row, currentCell.Column], shift, ctrl);
            }
            return true;
        }
    }
}
